/*
 * CmdWorker.cpp
 *
 *  Created on: Sep 11, 2011
 *      Author: Gherman Alin
 */

#include "CmdWorker.h"
#include "CmdCommand.h"
#include <map>
#include <boost/algorithm/string.hpp>

using namespace std;

namespace CommandLine {

CmdWorker::CmdWorker() :
		Threads::Thread(), in(cin), out(cout) {
}

CmdWorker::CmdWorker(istream& _in, ostream& _out) :
		Threads::Thread(), in(_in), out(_out) {
}

CmdWorker::~CmdWorker() {
	join();
}

void CmdWorker::run() {
	vector<string> strVec;
	vector<string>::iterator strVecIt;
	bool success;
	bool ok;
	string inputLine, msg;
	CmdType cmdType;
	do {
		getline(in, inputLine);
		CmdCommand cmd(inputLine);
		cmdType = cmd.getCmd();

		success = false;
		string *oldPass = cmd.getParam(PARAM_OLD_PASS);
		string *pass = cmd.getParam(PARAM_PASS);
		string *container = cmd.getParam(PARAM_CONTAINER);
		string contOrDefault = NULL == container ? "" : *container;
		string *key = cmd.getParam(PARAM_KEY);
		string strVal;
		vector<char> dataVal;

		string *newStrVal = cmd.getParam(PARAM_STR_VALUE);
		string *newDataVal = cmd.getParam(PARAM_DATA_VALUE);

		string *file = cmd.getParam(PARAM_PATH);

		switch (cmdType) {
		case CMD_SET_CONTAINER:
			if (NULL != oldPass && !secureFile.setContainer(contOrDefault, *oldPass)) {
				out << "old password is incorrect" << endl;
			}
			if ((NULL != container || NULL != pass)
					&& (ok = secureFile.setContainer(contOrDefault, pass == NULL ? "" : *pass))) {
				out << "container `" << contOrDefault << "` ";
				out << (ok ? (pass == NULL ? "set without password" : "set with password") :
				"cannot be changed password");
				out << endl;
				success = true;
			}
			break;
		case CMD_REMOVE_CONTAINER:
			if (container != NULL && secureFile.removeContainer(*container)) {
				out << "container `" << *container << "` removed" << endl;
				success = true;
			}
			break;
		case CMD_LIST_CONTAINERS:
			strVec = secureFile.getContainersNames();
			for (strVecIt = strVec.begin(); strVecIt != strVec.end(); strVecIt++) {
				out << *strVecIt << endl;
			}
			success = true;
			break;
		case CMD_LIST:
			strVec = secureFile.getKeys(contOrDefault);
			for (strVecIt = strVec.begin(); strVecIt != strVec.end(); strVecIt++) {
				out << *strVecIt << endl;
			}
			success = true;
			break;
		case CMD_GET:
			if (key != NULL) {
				if (secureFile.getStr(*key, contOrDefault, strVal)) {
					out << strVal << endl;
					success = true;
				}
				if (secureFile.getData(*key, contOrDefault, dataVal)) {
					throw "not implemented";
				}
			}
			break;
		case CMD_SET:
			if (NULL != key && NULL != newDataVal
					&& (ok = secureFile.set(*key, contOrDefault, *newDataVal))) {
				out << "data key `" << *key << "` added" << endl;
				success = true;
			}
			if (NULL != key && NULL != newStrVal
					&& (ok = secureFile.set(*key, contOrDefault, *newStrVal))) {
				out << "key `" << *key << "` and value `" << *newStrVal << "` added" << endl;
				success = true;
			}
			break;
		case CMD_REMOVE:
			if (NULL != key && secureFile.remove(*key, contOrDefault)) {
				out << "key `" << *key << "` deleted" << endl;
				success = true;
			}
			break;
		case CMD_LOAD_FILE:
			if (NULL != file && secureFile.load(*file)) {
				out << "file: `" << *file << "` loaded" << endl;
				success = true;
			}
			break;
		case CMD_SAVE_FILE:
			if (NULL != file && secureFile.save(*file)) {
				out << "file: `" << *file << "` saved" << endl;
				success = true;
			}
			break;
		case INVALID_CMD:
			out << "invalid command" << endl;
			break;
		default:
			break;
		}
		if (!success) {
			out << cmd.helpMsg() << endl;
		}
	}
	while (cmdType != CMD_QUIT);
}

}
